package com.wanghengzhi.design.patterns.creational.singleton;

/**
 * 单例模式
 * 单例模式（Singleton Pattern）是 Java 中最简单的设计模式之一。
 * 这种类型的设计模式属于创建型模式，它提供了一种创建对象的最佳方式。
 *
 * 这种模式涉及到一个单一的类，该类负责创建自己的对象，同时确保只有单个对象被创建。
 * 这个类提供了一种访问其唯一的对象的方式，可以直接访问，不需要实例化该类的对象。
 * @author wanghengzhi
 * @since 2020.11.24
 */
@SuppressWarnings("unused")
public class SingletonObject {

    private static final SingletonObject single = new SingletonObject();

    private SingletonObject() {

    }

    public static SingletonObject getInstance() {
        return single;
    }

    public void doSomething() {
        System.out.println("do something ... ");
    }
}

/**
 * 懒汉式，线程不安全
 */
@SuppressWarnings("unused")
class SingletonOne {
    private static SingletonOne singletonOne;

    private SingletonOne() {

    }
    public static SingletonOne getInstance() {
        if (singletonOne == null) {
            singletonOne = new SingletonOne();
        }
        return singletonOne;
    }
}

/**
 * 懒汉式，线程安全
 */
@SuppressWarnings("unused")
class SingletonTwo {
    private static SingletonTwo singletonTwo;
    private SingletonTwo (){
        
    }
    public static synchronized SingletonTwo getInstance() {
        if (singletonTwo == null) {
            singletonTwo = new SingletonTwo();
        }
        return singletonTwo;
    }
}

/**
 * 饿汉式
 */
@SuppressWarnings("unused")
class SingletonThree {
    private  static final SingletonThree singletonThree = new SingletonThree();
    private SingletonThree () {

    }
    public static SingletonThree getInstance() {
        return singletonThree;
    }
}

/**
 * 双检锁/双重校验锁（DCL，即 double-checked locking）
 */
@SuppressWarnings("unused")
class SingletonFour {
    private volatile static SingletonFour singletonFour;
    private SingletonFour(){

    }
    public static SingletonFour getInstance() {
        if (singletonFour == null) {
            synchronized (SingletonFour.class){
                if (singletonFour == null) {
                    singletonFour = new SingletonFour();
                }
            }
        }
        return  singletonFour;
    }
}

/**
 * 登记式/静态内部类
 */
@SuppressWarnings("unused")
class SingletonFive {
    private static class SingletonHolder {
        private static final SingletonFive INSTANCE  = new SingletonFive();
    }
    private SingletonFive () {

    }
    public static SingletonFive getInstance() {
        return SingletonHolder.INSTANCE;
    }
}

/**
 * 枚举 推荐。
 */
enum SingletonSix {
    /**
     * 实例对象
     */
    INSTANCE;
    public void doSomething () {
        System.out.println("do something ...");
    }
}
